//  Copyright 2011 Charlie Garrett
//
//  Licensed under the Apache License, Version 2.0 (the "License");
//  you may not use this file except in compliance with the License.
//  You may obtain a copy of the License at
//
//  http://www.apache.org/licenses/LICENSE-2.0
//
//  Unless required by applicable law or agreed to in writing, software
//  distributed under the License is distributed on an "AS IS" BASIS,
//  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
//  See the License for the specific language governing permissions and
//  limitations under the License.
//
//  logic.h
//

#ifndef LOGIC_H
#define LOGIC_H

#include <iostream>
#include <string>
#include <vector>

#include "assert.h"

// The initial framework of a logic programming toolkit to be built on LLVM.
//
// The first piece is a Prolog interpreter using a Warren Abstract Machine
// architecture, as described by Hassan Ait-Kaci's "Warren's Abstract Machine
// A Tutorial Reconstruction".

// Ideas
// 1) It should be possible to compute, bottom-up, some sets of terms that will or won't unify and
//    use them to shortcut the normal unification routine.
//
// 2) Can we do register allocation, term ordering and instruction emission all at the same time?
//

// TODO: Find the proper place to uniquify Terms.
// Union/Find algorithm in Term constructors, parser?

namespace logic {
    using namespace std;
    
    class Program;
    
    void TestL0Interpreter();    
    void TestInterpreter();        
    
    void TestInput();
    
    void InterpretProgram(const char *filename, bool trace = false, bool interactive = false);

    void StartShell(Program *program, bool trace);
}  // namespace logic

#endif  // LOGIC_H